home *** CD-ROM | disk | FTP | other *** search
/ PC Plus SuperCD (UK) 1997 May / PC Plus Super CD Issue 127 (May 1997).iso / vcafe / samples.bin / Calendar.java < prev    next >
Encoding:
Java Source  |  1996-09-04  |  17.7 KB  |  617 lines

  1. /*
  2.  * Title: Calendar
  3.  * Type: Applet
  4.  * Source: Calendar.java
  5.  * Application Description: Display a calendar window with the
  6.  * month/year selected by the user.  When a date is selected,
  7.  * a scrolling text box is displayed at the top along with the
  8.  * event information for that date. Event information is input
  9.  * and extracted from HTML. The format for the "date:event"
  10.  * HTML is the following:
  11.  *
  12.  *      param name=EVENT1 value="01/23/96:January 23, 1996 - Bake Sale"
  13.  *      param name=EVENT2 value="01/30/96:January 30, 1996 - Ski Vacation"
  14.  *
  15.  * NOTE:  The date and event string information are separated by a
  16.  * colon (:); the format for the date MUST be MM/DD/YY.
  17.  *
  18.  * Symantec Corporation.
  19.  */
  20.  
  21. import java.applet.Applet;
  22. import java.awt.*;
  23. import java.awt.Font;
  24. import java.util.Date;
  25. import java.util.Hashtable;
  26. import java.lang.String;
  27.  
  28. /**
  29.  * The main applet class
  30.  */
  31.  
  32. public class Calendar extends Applet implements Runnable
  33. {
  34.         Button myButton[];                  // The calendar date buttons
  35.         Image bannerText;                   // The banner text display object
  36.         MyCanvas textCanvas;                // The banner text display object
  37.         boolean loaded = true;
  38.         Graphics textGC;
  39.  
  40.         //TextField date;                     // Date display text field
  41.         int thismonth;                      // App. variable
  42.         int thisyear;                       // App. variable
  43.         int days;                           // App. variable
  44.         int dayselected;                    // App. variable
  45.         Date dateSelected;                  // User-selected Date object
  46.         int buttonShift;                    // Used to determine what day the
  47.                                             // 1st of the month falls on
  48.  
  49.         Hashtable eventHash;                // Used to track date/event combinations
  50.  
  51.         //Thread related variables.
  52.         Thread bannerThread;                // The main banner thread
  53.         int maxWidth;                       // The width of the banner window
  54.         int maxHeight;                      // The height of the banner window
  55.         int bannerHeight = 20;              // The height of the banner text
  56.            public String message;              // The string displayed on the banner
  57.            int msgX = 0;                       // X-coordinate of the banner string
  58.            int msgY = 0;                       // Y-coordinate of the banner string
  59.            int msgWidth = 0;                   // This is the width of the message in pixels
  60.            public Dimension lastS = new Dimension(1, 1);
  61.            public Font msgFont;                // The font used in the banner
  62.            static boolean loadedtext = true;
  63.  
  64.         /**
  65.          *  Set up the three main panels (top,middle,lower) along with the
  66.          *  UI components (calendar buttons, etc.)
  67.          */
  68.  
  69.         public void init()
  70.         {
  71.             message = "Welcome to the Java Calendar!!!";
  72.  
  73.             eventHash = new Hashtable();
  74.             getParamData();
  75.  
  76.             setLayout(new BorderLayout());
  77.  
  78.             //Set up the banner...
  79.             bannerText = createImage(300,20);
  80.             textGC = bannerText.getGraphics();
  81.             textGC.setColor(Color.blue);
  82.             textGC.fillRect(4, 4, 300, 20);
  83.             textGC.setColor(Color.white);
  84.  
  85.             textCanvas = new MyCanvas(bannerText);
  86.             textCanvas.resize(300, 25);
  87.  
  88.             //Set up the center (calendar) panel...
  89.             Label sunday, monday, tuesday, wednesday, thursday, friday, saturday;
  90.             sunday = new Label("Sun");
  91.             monday = new Label("Mon");
  92.             tuesday = new Label("Tue");
  93.             wednesday = new Label("Wed");
  94.             thursday = new Label("Thu");
  95.             friday = new Label("Fri");
  96.             saturday = new Label("Sat");
  97.  
  98.             Panel datePanel = new Panel();
  99.             datePanel.setLayout(new GridLayout(7, 7));
  100.  
  101.             datePanel.add(sunday);
  102.             datePanel.add(monday);
  103.             datePanel.add(tuesday);
  104.             datePanel.add(wednesday);
  105.             datePanel.add(thursday);
  106.             datePanel.add(friday);
  107.             datePanel.add(saturday);
  108.  
  109.             myButton=new Button[42];
  110.             for(int i = 0; i < 42; i++)
  111.             {
  112.               myButton[i] = new Button("");
  113.               datePanel.add(myButton[i]);
  114.             }
  115.  
  116.             //{{INIT_CONTROLS
  117.         setLayout(new FlowLayout(FlowLayout.CENTER,5,5));
  118.         addNotify();
  119.         resize(430,270);
  120.         selPanel = new java.awt.Panel();
  121.         selPanel.setLayout(new FlowLayout(FlowLayout.CENTER,5,5));
  122.         selPanel.reshape(3,76,321,54);
  123.         selPanel.setFont(new Font("Dialog", Font.PLAIN, 12));
  124.         add(selPanel);
  125.         leftButton = new java.awt.Button("<<<");
  126.         leftButton.reshape(18,18,63,26);
  127.         selPanel.add(leftButton);
  128.         date = new java.awt.TextField(15);
  129.         date.reshape(94,18,130,26);
  130.         selPanel.add(date);
  131.         rightButton = new java.awt.Button(">>>");
  132.         rightButton.reshape(237,18,63,26);
  133.         selPanel.add(rightButton);
  134.         //}}
  135.  
  136.             date.setEditable(false);
  137.  
  138.             add("North", textCanvas);
  139.             add("Center", datePanel);
  140.  
  141.             textCanvas.resize(299, 25);
  142.             datePanel.resize(299, 225);
  143.             selPanel.resize(299, 25);
  144.         }
  145.  
  146.         /**
  147.          * Find out today's date and set up the calendar to display the correct
  148.          * month and year
  149.          */
  150.  
  151.         public void start()
  152.         {
  153.             Date todaydate = new Date();
  154.             setMonthString(todaydate);
  155.             setCalendar(todaydate);
  156.  
  157.             //Establish the font size and characteristics for the banner
  158.             CreateBannerParams();
  159.  
  160.             bannerThread = new Thread(this);
  161.             bannerThread.start();
  162.         }
  163.  
  164.  
  165.         /**
  166.          * The paint function is used to draw the text string which is
  167.          * displayed along the top of the calendar.
  168.          */
  169.  
  170.         public void paint(Graphics g)
  171.         {
  172.             g.drawImage(bannerText, 0, 0, this);
  173.         }
  174.  
  175.         /**
  176.          * Handle the events of the date-selection buttons as well as the
  177.          * buttons corresponding to specific days.
  178.          */
  179.  
  180.         public boolean action(Event e, Object arg)
  181.         {
  182.             if(e.target instanceof Button)
  183.             {
  184.                 if(">>>" == arg)
  185.                 {
  186.                     incrementCalendar();
  187.                 } else if("<<<" == arg)
  188.                 {
  189.                     decrementCalendar();
  190.                 } else if (arg != "")
  191.                 {
  192.                     Integer tempInt = Integer.valueOf((String)arg);
  193.                     dayselected = tempInt.intValue();
  194.                     dateSelected = getDateSelected();
  195.                     displayBannerText(dateSelected);
  196.                     repaint();
  197.                  }
  198.             }
  199.             return false;
  200.         }
  201.  
  202.  
  203.         /**
  204.          * Given a Date, set up the calendar elements to display the
  205.          * appropriate dates on the appropriate calendar buttons.
  206.          */
  207.  
  208.         private void setCalendar(Date dt)
  209.         {
  210.             //clear calendar
  211.             for(int i = 0; i < 42; i++)
  212.             {
  213.                 myButton[i].setLabel("");
  214.             }
  215.  
  216.             int thisMo = dt.getMonth();
  217.             int thisDy = dt.getDay();
  218.             int thisYr = dt.getYear();
  219.  
  220.             //Find the day of the week of the first
  221.             Date firstday = new Date(thisYr, thisMo, 1);
  222.             int dayoffirst = firstday.getDay();
  223.             buttonShift = dayoffirst;
  224.  
  225.             int dayspermonth = getDaysPerMonth(thisMo);
  226.             for(int i = 1; i < dayspermonth+1; i++)
  227.             {
  228.                 myButton[i+buttonShift-1].setLabel(Integer.toString(i));
  229.             }
  230.         }
  231.  
  232.  
  233.         /**
  234.          * Given a Date, set the text field to display it as a
  235.          * string containing the month and the year.
  236.          */
  237.  
  238.         private void setMonthString(Date dt)
  239.         {
  240.             thismonth = dt.getMonth();
  241.             thisyear = dt.getYear();
  242.  
  243.             String monthstring;
  244.  
  245.             switch(thismonth)
  246.             {
  247.                 case 0:
  248.                     monthstring = "January";
  249.                     break;
  250.                 case 1:
  251.                     monthstring = "February";
  252.                     break;
  253.                 case 2:
  254.                     monthstring = "March";
  255.                     break;
  256.                 case 3:
  257.                     monthstring = "April";
  258.                     break;
  259.                 case 4:
  260.                     monthstring = "May";
  261.                     break;
  262.                 case 5:
  263.                     monthstring = "June";
  264.                     break;
  265.                 case 6:
  266.                     monthstring = "July";
  267.                     break;
  268.                 case 7:
  269.                     monthstring = "August";
  270.                     break;
  271.                 case 8:
  272.                     monthstring = "September";
  273.                     break;
  274.                 case 9:
  275.                     monthstring = "October";
  276.                     break;
  277.                 case 10:
  278.                     monthstring = "November";
  279.                     break;
  280.                 case 11:
  281.                     monthstring = "December";
  282.                     break;
  283.                  default:
  284.                     monthstring = "Month";
  285.                     break;
  286.                 }
  287.             String temp = (monthstring +" ");
  288.             temp = temp + (Integer.toString(1900 + thisyear));
  289.             date.setText(temp);
  290.         }
  291.  
  292.  
  293.         /**
  294.          * Increments the calendar (both Mo/Yr text field and date buttons)
  295.          * to the next sequential month/year combination.
  296.          */
  297.  
  298.         private void incrementCalendar()
  299.         {
  300.             thismonth += 1;
  301.             if(thismonth > 12)
  302.             {
  303.                 thismonth = 0;
  304.                 thisyear += 1;
  305.             }
  306.             Date incDate = new Date(thisyear, thismonth, 1);
  307.             setMonthString(incDate);
  308.             setCalendar(incDate);
  309.         }
  310.  
  311.         /**
  312.          * Decrements the calendar (both Mo/Yr text field and date buttons)
  313.          * to the previous sequential month/year combination.
  314.          */
  315.  
  316.         private void decrementCalendar()
  317.         {
  318.             thismonth -= 1;
  319.             if(thismonth < 0)
  320.             {
  321.                 thismonth = 11;
  322.                 thisyear -= 1;
  323.             }
  324.             Date decDate = new Date(thisyear, thismonth, 1);
  325.             setMonthString(decDate);
  326.             setCalendar(decDate);
  327.         }
  328.  
  329.         /**
  330.          * Given a month (represented as an integer), return the
  331.          * number of days in that month (corrects for leap years).
  332.          */
  333.  
  334.         private int getDaysPerMonth(int m)
  335.         {
  336.             switch(m)
  337.             {
  338.                 case 0:
  339.                     days = 31;
  340.                     break;
  341.  
  342.                 case 1:
  343.                     //Correct for a leap year
  344.                     int tempYear = 1900 + thisyear;
  345.                     if((tempYear % 4) == 0)         // Could be leap
  346.                     {
  347.                         if((tempYear % 100) == 0 && // Centuries aren't
  348.                            (tempYear % 400) != 0)   // Except every 4th
  349.                             days = 28;
  350.                         else
  351.                             days = 29;
  352.                         break;
  353.                     }
  354.                     days = 28;
  355.                     break;
  356.  
  357.                 case 2:
  358.                     days = 31;
  359.                     break;
  360.  
  361.                 case 3:
  362.                     days = 30;
  363.                     break;
  364.                 case 4:
  365.                     days = 31;
  366.                     break;
  367.  
  368.                 case 5:
  369.                     days = 30;
  370.                     break;
  371.  
  372.                 case 6:
  373.                     days = 31;
  374.                     break;
  375.  
  376.                 case 7:
  377.                     days = 31;
  378.                     break;
  379.  
  380.                 case 8:
  381.                     days = 30;
  382.                     break;
  383.  
  384.                 case 9:
  385.                     days = 31;
  386.                     break;
  387.  
  388.                 case 10:
  389.                     days = 30;
  390.                     break;
  391.  
  392.                 case 11:
  393.                     days = 31;
  394.                     break;
  395.  
  396.                 default:
  397.                     days = 31;
  398.                     break;
  399.              }
  400.               return days;
  401.         }
  402.  
  403.         /**
  404.          * return the date that was selected by pushing a button
  405.          * on the calendar
  406.          */
  407.  
  408.         private Date getDateSelected()
  409.         {
  410.             dateSelected = new Date(thisyear, thismonth, dayselected);
  411.             return dateSelected;
  412.         }
  413.  
  414.         /**
  415.          * Given a date, set the banner text message
  416.          */
  417.  
  418.         private void displayBannerText(Date dt)
  419.         {
  420.             message = (String)eventHash.get(dt);
  421.  
  422.             if(message == null)
  423.             {
  424.                 int tempMo = (dt.getMonth()) + 1;
  425.                 int tempYr = (dt.getYear());
  426.                 int tempDy = (dt.getDate());
  427.                 message = "You selected ";
  428.                 message += Integer.toString(tempMo);
  429.                 message += "/" + Integer.toString(tempDy);
  430.                 message += "/" + Integer.toString(tempYr);
  431.             }
  432.             CreateBannerParams();
  433.          }
  434.  
  435.         /**
  436.          * An initialization function designed to get parameter info,
  437.          */
  438.  
  439.         private void getParamData()
  440.         {
  441.             String param = null;
  442.             boolean datapresent = true;
  443.             int i = 1;
  444.  
  445.             while(datapresent)
  446.             {
  447.                 try
  448.                 {
  449.                     param = getParameter("EVENT"+ Integer.toString(i));
  450.                 } catch(Exception e)
  451.                 {
  452.                     System.out.println(e);
  453.                 }
  454.  
  455.                 if(param == null)
  456.                 {
  457.                     datapresent = false;
  458.                 } else
  459.                 {
  460.                     i += 1;
  461.                     parseHashData(param);
  462.                 }
  463.             }
  464.         }
  465.  
  466.  
  467.         /**
  468.          * A small utility to take the param info, turn it into program-friendly
  469.          * classes and strings and then put all that info into a hash table.
  470.          * The string fed to parseHashData is the raw param string from the HTML.
  471.          */
  472.  
  473.         private void parseHashData(String str)
  474.         {
  475.             //Separate the param string into its date/event components
  476.             int sep = str.indexOf(':');
  477.             String evt = str.substring(sep+1);
  478.             String evtdate = str.substring(0, sep);
  479.  
  480.             //make the evtdate into a date class format (YY/MM/DD). The input
  481.             //string is in the U.S.-style MM/DD/YY format.
  482.  
  483.             int sel1 = evtdate.indexOf('/');
  484.             int sel2 = evtdate.lastIndexOf('/');
  485.  
  486.             String mo = evtdate.substring(0, sel1);
  487.             String dy = evtdate.substring(sel1+1, sel2);
  488.             String yr = evtdate.substring(sel2+1);
  489.  
  490.             int intMo = Integer.parseInt(mo);
  491.             int intDay = Integer.parseInt(dy);
  492.             int intYr = Integer.parseInt(yr);
  493.  
  494.             Date newDate = new Date(intYr, intMo-1, intDay);
  495.  
  496.             // Put the evt and evtdate info into a Hashtable
  497.             eventHash.put(newDate, evt);
  498.         }
  499.  
  500.     /**
  501.      * The main thread event function
  502.      */
  503.  
  504.     public void run()
  505.     {
  506.         Thread me = Thread.currentThread();
  507.         me.setPriority(Thread.MIN_PRIORITY);
  508.  
  509.         repaint();
  510.  
  511.           while(loadedtext)
  512.             {
  513.               drawText();
  514.               nextPos();
  515.  
  516.               textCanvas.repaint();
  517.  
  518.               try
  519.               {
  520.                  Thread.sleep(150);
  521.               }  catch(InterruptedException e)
  522.               {}
  523.             }
  524.     }
  525.  
  526.     /**
  527.      * Draws the appropriate text string onto the (invisible) textGC
  528.      * graphics context. Used prior to a repaint request.
  529.      */
  530.  
  531.     public synchronized void drawText()
  532.     {
  533.         if(loadedtext)
  534.         {
  535.            //following code for banner...
  536.            textGC.setColor(Color.blue);
  537.            textGC.fillRect(0, 0, 300, bannerHeight);
  538.            textGC.setColor(Color.white);
  539.            textGC.setFont(msgFont);
  540.            textGC.drawString(message, msgX, msgY);
  541.         }
  542.     }
  543.  
  544.     /**
  545.      * Scrolls the banner text one "position" to the left.
  546.      */
  547.  
  548.     public synchronized void nextPos()
  549.     {
  550.          msgX -= 10;
  551.          if((msgX + msgWidth) < 0)
  552.          {
  553.               msgX = lastS.width;
  554.          }
  555.          repaint();
  556.     }
  557.  
  558.  
  559.     /**
  560.      * Create the original banner parameters (font size, etc.)
  561.      */
  562.  
  563.     public void CreateBannerParams()
  564.     {
  565.         int w = 300;
  566.         int h = 20;
  567.         lastS.width = w;
  568.         lastS.height = h;
  569.  
  570.         int refH = 14;
  571.         Font tf = new Font("TimesRoman", Font.BOLD, refH);
  572.         textGC.setFont(tf);
  573.         FontMetrics tfm = textGC.getFontMetrics(tf);
  574.         int fh = tfm.getHeight();
  575.         fh = refH*(h-2)/fh;
  576.         msgFont = new Font("TimesRoman", Font.BOLD, fh);
  577.         FontMetrics fm = textGC.getFontMetrics(msgFont);
  578.         fh = fm.getHeight();
  579.         msgX = w;
  580.         msgY = ((h-fh) >> 1) + fm.getAscent();
  581.         msgWidth = fm.stringWidth(message);
  582.     }
  583.         //{{DECLARE_CONTROLS
  584.     java.awt.Panel selPanel;
  585.     java.awt.Button leftButton;
  586.     java.awt.TextField date;
  587.     java.awt.Button rightButton;
  588.     //}}
  589.  
  590. }
  591.  
  592.  
  593.  
  594. /**
  595.  * Subclasses Canvas object which allows display of running (banner) text
  596.  */
  597.  
  598. class MyCanvas extends Canvas
  599. {
  600.     Image im;
  601.  
  602.     MyCanvas(Image img)
  603.     {
  604.         im = img;
  605.     }
  606.  
  607.     public void paint(Graphics g)
  608.     {
  609.         g.drawImage(im, 0, 0, this);
  610.     }
  611.  
  612.     public void update(Graphics g)
  613.     {
  614.         paint(g);
  615.     }
  616. }
  617.